/**
 * 
 */
package com.dalonedrow.engine.ui.base.menu;

import java.util.ArrayList;

import com.dalonedrow.engine.systems.JOGLErrorHandler;
import com.dalonedrow.engine.ui.base.GuiComponentImpl;
import com.dalonedrow.engine.ui.base.GuiComponentLibrary;
import com.dalonedrow.engine.ui.base.GuiSelectable;
import com.dalonedrow.engine.ui.base.GuiSelectableGroup;
import com.dalonedrow.pooled.PooledStringBuilder;
import com.dalonedrow.pooled.StringBuilderPool;

/**
 * @author Donald
 */
public abstract class MenuGroup extends GuiComponentImpl
		implements GuiSelectableGroup {
	/** the component's id. */
	private int				id;
	protected MenuGroup() {
		id = GuiComponentLibrary.getInstance().getNextId();		
	}
	@Override
	public final int getId() {
		return id;
	}
	/** the list of {@link MenuItem}s in this <code>MenuGroup</code>. */
	private ArrayList<MenuItem>	items	= new ArrayList<MenuItem>();
	/**
	 * {@inheritDoc}
	 */
	@Override
	public final void addItem(final GuiSelectable item) throws Exception {
		if (!(item instanceof MenuItem)) {
			PooledStringBuilder text =
					StringBuilderPool.getInstance().getStringBuilder();
			text.append("Invalid class being added to MenuGroup. Cannot add ");
			text.append(item.getClass().getCanonicalName());
			Exception ex = new Exception(text.toString());
			text.returnToPool();
			throw ex;
		}
		items.add((MenuItem) item);
	}
	/**
	 * {@inheritDoc}
	 */
	public void animate() {
		// TODO Auto-generated method stub

	}
	/**
	 * {@inheritDoc}
	 */
	@Override
	public final void clear() {
		items.clear();
	}
	/**
	 * {@inheritDoc}
	 */
	@Override
	public final void clearHighlight() {
		for (int i = 0; i < items.size(); i++) {
			items.get(i).removeHighlight();
		}
	}
	/**
	 * {@inheritDoc}
	 */
	@Override
	public final GuiSelectable findItem(final int id) {
		GuiSelectable item = null;
		for (int i = 0; i < items.size(); i++) {
			if (items.get(i).getId() == id) {
				item = items.get(i);
				break;
			}
		}
		return item;
	}
	/**
	 * {@inheritDoc}
	 */
	public final GuiSelectable findItemByIndex(final int id) {
		return items.get(id);
	}
	/**
	 * {@inheritDoc}
	 */
	@Override
	public final int findItemIndex(final float x, final float y) {
		int index = -1;
		for (int i = 0; i < items.size(); i++) {
			if (items.get(i).isInHotSpot(x, y)) {
				index = i;
				break;
			}
		}
		return index;
	}
	/**
	 * {@inheritDoc}
	 */
	@Override
	public final int findItemIndex(final int id) {
		int index = -1;
		for (int i = 0; i < items.size(); i++) {
			if (items.get(i).getId() == id) {
				index = i;
				break;
			}
		}
		return index;
	}
	/**
	 * {@inheritDoc}
	 */
	@Override
	public final GuiSelectable getHighlighted() {
		GuiSelectable item = null;
		if (super.isVisible()) {
			for (int i = 0; i < items.size(); i++) {
				if (items.get(i).isHighlighted()) {
					item = items.get(i);
					break;
				}
			}
		}
		return item;
	}
	/**
	 * {@inheritDoc}
	 */
	@Override
	public final int getHighlightedIndex() {
		int item = -1;
		if (super.isVisible()) {
			for (int i = 0; i < items.size(); i++) {
				if (items.get(i).isHighlighted()) {
					item = i;
					break;
				}
			}
		}
		return item;
	}
	/**
	 * Gets a specific {@link MenuItem} by its index.
	 * @param index the {@link MenuItem}'s index
	 * @return {@link MenuItem}
	 */
	protected final MenuItem getItem(final int index) {
		return items.get(index);
	}
	/**
	 * Gets the number of items contained in the {@link MenuGroup}.
	 * @return int
	 */
	protected final int getNumItems() {
		return items.size();
	}
	/**
	 * {@inheritDoc}
	 */
	@Override
	public final boolean highlightIndex(final int index) {
		clearHighlight();
		boolean val = false;
		try {
			val = items.get(index).onHighlight(true);
		} catch (ArrayIndexOutOfBoundsException aioobex) {
			val = false;
		} catch (Exception ex) {
			JOGLErrorHandler.getInstance().fatalError(ex);
		}
		return val;
	}
	/**
	 * {@inheritDoc}
	 */
	@Override
	public final boolean highlightItem(final int id) {
		clearHighlight();
		GuiSelectable item = null;
		boolean done = false;
		for (int i = 0; i < items.size(); i++) {
			if (items.get(i).getId() == id) {
				item = items.get(i);
				break;
			}
		}
		if (item != null) {
			done = item.onHighlight(true);
		}
		return done;
	}
	/**
	 * {@inheritDoc}
	 */
	@Override
	public final boolean highlightNext() {
		int index = 0;
		for (int i = 0; i < items.size(); i++) {
			if (items.get(i).isHighlighted()) {
				index = i;
				break;
			}
		}
		clearHighlight();
		index++;
		if (index >= items.size()) {
			index = 0;
		}
		return highlightIndex(index);
	}
	/**
	 * {@inheritDoc}
	 */
	@Override
	public final boolean highlightPrevious() {
		int index = 0;
		for (int i = 0; i < items.size(); i++) {
			if (items.get(i).isHighlighted()) {
				index = i;
				break;
			}
		}
		clearHighlight();
		index--;
		if (index < 0) {
			index = items.size() - 1;
		}
		return highlightIndex(index);
	}
	/**
	 * {@inheritDoc}
	 */
	@Override
	public final boolean isInHotSpot(final float x, final float y) {
		boolean isIn = false;
		if (super.isVisible() && super.isActive()) {
			for (int i = 0; i < items.size(); i++) {
				if (items.get(i).isInHotSpot(x, y)) {
					isIn = true;
					break;
				}
			}
		}
		return isIn;
	}
	/**
	 * {@inheritDoc}
	 */
	public void move() {
		// TODO Auto-generated method stub

	}
	/**
	 * {@inheritDoc}
	 */
	@Override
	public final boolean onHighlight(final boolean highlighted) {
		return false;
	}
	/**
	 * {@inheritDoc}
	 */
	@Override
	public final boolean onSelect() {
		return false;
	}
	/**
	 * {@inheritDoc}
	 */
	@Override
	public final boolean setFocus(final float x, final float y) {
		return false;
	}
	/**
	 * {@inheritDoc}
	 */
	@Override
	public final void setVisible(final boolean value) {
		super.setVisible(value);
		for (int i = 0; i < items.size(); i++) {
			items.get(i).setVisible(value);
		}
	}
	/**
	 * {@inheritDoc}
	 */
	public void update() {
		// TODO Auto-generated method stub

	}
	/**
	 * {@inheritDoc}
	 */
	public void update(final long delta) {
		// TODO Auto-generated method stub

	}
}
